package de.jmda.core.mproc;

import static java.util.Arrays.asList;
import static org.junit.Assert.fail;

import java.io.File;
import java.util.ArrayList;
import java.util.List;

import org.apache.log4j.Logger;
import org.junit.Before;

import de.jmda.core.mproc.LaunchConfiguration;
import de.jmda.core.mproc.Launcher;
import de.jmda.core.mproc.Processor;
import de.jmda.core.util.FileUtil;

public abstract class AbstractJUTProcessors
{
	private final static Logger LOGGER =
      Logger.getLogger(AbstractJUTProcessors.class);

	@Before
	public void setUp() throws Exception
	{
		LaunchConfiguration launchConfiguration = new LaunchConfiguration();

		launchConfiguration.files.addAll(getJavaFilesWithSupportedAnnotations());
		launchConfiguration.processors.addAll(getProcessors());

		if (false == Launcher.launch(launchConfiguration))
		{
			fail(
					  "unexpected return value [false] for launch of processors from "
					+ getClass().getName());
		}
	}

	protected abstract List<? extends Processor> getProcessors();

	/**
	 * Default implementation that returns a list with a single java type source
	 * file object. The file object likely represents the source code for the
	 * currently running test. So if there are annotated elements in the source
	 * file of the currently running test the processor returned by {@link
	 * #getProcessors()} is ready to be launched.
	 *
	 * @return file objects representing annotated java type source files
	 */
	protected List<File> getJavaFilesWithSupportedAnnotations()
	{
		File file =
				new File(
						  getSourceRoot().getAbsolutePath()
						+ File.separator
						+ FileUtil.toSourceFilePath(getClass()));
		
		if (file.exists())
		{
			return asList(new File[] { file });
		}

		LOGGER.warn(
				"default java file [" + file.getAbsolutePath() + "] that is supposed " +
				"to contain elements annotated with supported annotations does not " +
				"exist, returning empty list");

		return new ArrayList<>();
	}

	protected File getSourceRoot()
	{
		return new File("../jmda.core/src/test/java");
	}
}